package com.io.commonlink.http

import com.io.commonlib.enum.NetworkType
import com.io.commonlib.helper.CommonDeviceHelper
import com.io.commonlib.helper.LogHelper
import okhttp3.*
import okhttp3.MediaType.Companion.toMediaType
import okhttp3.RequestBody.Companion.toRequestBody
import java.io.IOException
import java.net.URLEncoder
import java.util.HashMap
import java.util.concurrent.TimeUnit
import kotlin.coroutines.resume
import kotlin.coroutines.resumeWithException
import kotlin.coroutines.suspendCoroutine

/**
 * 封装okhttp的 get/set方法
 */
object OkHttpHelper {
    private val TAG = OkHttpHelper::class.java.simpleName
    private lateinit var client:OkHttpClient
    private val mediaType = "application/json; charset=utf-8".toMediaType()
    private val REQUEST_OUT_TIME = 15L

    init {
        client = OkHttpClient.Builder()
            .addInterceptor(LogInterceptor())
            .connectTimeout(REQUEST_OUT_TIME, TimeUnit.SECONDS)
            .build()
    }

    /**
     * 发送post请求
     */
    @Throws(IOException::class)
    private fun sendPost(url: String, json: String, callback: Callback) {
        val requestBody = json.toRequestBody(mediaType)
        val request = Request.Builder()
            .url(url)
            .post(requestBody)
            .build()
        client.newCall(request).enqueue(callback)
        client.interceptors
    }

    /**
     * 发送get请求
     */
    private fun sendGet(url: String, params: HashMap<String, String>, callback: Callback) {
        val paramStr = getParams(params)
        val request = Request.Builder()
            .url(url + paramStr)
            .build()
        client.newCall(request).enqueue(callback)
    }

    /**
     * 使用协程封装Post网络请求
     */
    suspend fun coroutineSendPost(address: String, json: String): String {
        return suspendCoroutine { continuation ->
            sendPost(address, json, object : Callback {
                override fun onResponse(call: Call, response: Response) {
                    try {
                        response.body?.let {
                            if(response.code == 200){
                                continuation.resume(it.string())
                            }
                            else{
                                val exception = Exception(it.string())
                                continuation.resumeWithException(exception)
                            }
                        }?: let {
                            val exception = Exception("response.body为null")
                            continuation.resumeWithException(exception)
                        }
                    } catch (e: Exception) {
                        continuation.resumeWithException(e)
                    }
                }

                override fun onFailure(call: Call, e: IOException) {
                    continuation.resumeWithException(e)
                }
            })
        }
    }

    /**
     * 使用协程封装Post网络请求
     */
    suspend fun coroutineSendGet(address: String, params: HashMap<String, String>): String {
        return suspendCoroutine { continuation ->
            sendGet(address, params, object : Callback {
                override fun onResponse(call: Call, response: Response) {
                    try {
                        response.body?.let {
                            if(response.code == 200){
                                continuation.resume(it.string())
                            }
                            else{
                                val exception = Exception(it.string())
                                continuation.resumeWithException(exception)
                            }
                        }?: let {
                            val exception = Exception("response.body为null")
                            continuation.resumeWithException(exception)
                        }
                    } catch (e: Exception) {
                        continuation.resumeWithException(e)
                    }
                }

                override fun onFailure(call: Call, e: IOException) {
                    continuation.resumeWithException(e)
                }
            })
        }
    }

    /**
     * 将json格式的参数转换成字符串
     */
    private fun getParams(params: HashMap<String, String>?): String {
        var result = ""
        params?.let {
            try {
                val paramStr = StringBuilder("?")
                for (entry in params.entries) {
                    val entryKey = URLEncoder.encode(entry.key, "UTF-8")
                    val entryValue = URLEncoder.encode(entry.value, "UTF-8")
                    paramStr.append(entryKey).append("=").append(entryValue).append("&")
                }
                result = paramStr.substring(0, paramStr.length - 1)
            } catch (e: Exception) {
                e.printStackTrace()
            }
        }
        return result
    }
}